package com.ctshk.rpc.system.service.impl;

import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONObject;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ctshk.common.dto.Result;
import com.ctshk.common.enums.IsDeletedCode;
import com.ctshk.common.enums.NumberConstant;
import com.ctshk.common.enums.SystemError;
import com.ctshk.common.exception.BusinessException;
import com.ctshk.common.model.PageResponse;
import com.ctshk.common.model.TokenUser;
import com.ctshk.common.utils.*;
import com.ctshk.rpc.scenic.service.IScenicProductService;
import com.ctshk.rpc.system.dto.AreaDTO;
import com.ctshk.rpc.system.dto.ChimeLongScenicDTO;
import com.ctshk.rpc.system.dto.OperationLogDTO;
import com.ctshk.rpc.system.dto.ScenicDTO;
import com.ctshk.rpc.system.entity.OperationLog;
import com.ctshk.rpc.system.entity.Scenic;
import com.ctshk.rpc.system.entity.SysArea;
import com.ctshk.rpc.system.enums.ScenicEnum;
import com.ctshk.rpc.system.mapper.MainDataCollectionTouristTypeMapper;
import com.ctshk.rpc.system.mapper.OperationLogMapper;
import com.ctshk.rpc.system.mapper.ScenicMapper;
import com.ctshk.rpc.system.mapper.SysAreaMapper;
import com.ctshk.rpc.system.req.*;
import com.ctshk.rpc.system.service.ISceneService;
import com.ctshk.rpc.system.service.ISysAreaService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.beans.factory.annotation.Autowired;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * <p>
 *
 * </p>
 *
 * @author xuhui
 * @since 1/27/2021
 */
@DubboService
@Slf4j
public class SceneServiceImpl extends ServiceImpl<ScenicMapper, Scenic> implements ISceneService {

    @Autowired
    ScenicMapper scenicMapper;

    @Autowired
    SysAreaMapper sysAreaMapper;

    @Autowired
    OperationLogMapper operationLogMapper;

    @Autowired
    MainDataCollectionTouristTypeMapper mainDataCollectionTouristTypeMapper;
    @Autowired
    ISysAreaService sysAreaService;
    @DubboReference
    IScenicProductService iScenicProductService;


    @Override
    public Result add(ScenicAddReq scenicAddReq, TokenUser currentUser) {
        //根据景点中文名判断景点是否重复
        QueryWrapper<Scenic> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(Scenic::getLat,scenicAddReq.getLat());
        queryWrapper.lambda().eq(Scenic::getLon,scenicAddReq.getLon());
        queryWrapper.eq("is_deleted", NumberConstant.ZERO.getValue());
        Scenic scenic = scenicMapper.selectOne(queryWrapper);
        if (scenic != null) {
            return Result.failed(SystemError.MAINDATA_4018);
        }
        //新增景点
        Scenic scenicAdd = EntityUtil.copy(scenicAddReq, Scenic.class);
        scenicAdd.setScenicLevel(scenicAddReq.getScenicLevel());
        scenicAdd.setScenicLocation(scenicAddReq.getScenicLocation());
        scenicAdd.setCreateId(currentUser.getId());
        scenicAdd.setGmtCreate(LocalDateTime.now());
        scenicAdd.setStatus(0);//默认有效
        scenicAdd.setIsDeleted(NumberConstant.ZERO.getValue());
        scenicAdd.setId(SnowflakeIdWorker.nextId());
        List<PhotoReq> photoJson = scenicAddReq.getPhotoJson();
        String photoStr = JSON.toJSONString(photoJson);
        scenicAdd.setPhotoJson(photoStr);
        SysArea area = getAreaName(scenicAddReq.getAreaName());
        if(area != null){
            scenicAdd.setAreaId(area.getId());
            scenicAdd.setAreaName(area.getProvinceTraditional());
        }
        scenicMapper.insert(scenicAdd);
        return Result.success();
    }

    @Override
    public Result update(ScenicUpdateReq scenicUpdateReq, TokenUser currentUser) {
        Scenic scenic = scenicMapper.selectById(scenicUpdateReq.getId());
        if ((scenic != null) && scenic.getIsDeleted().equals(NumberConstant.ZERO.getValue())) {
            Scenic scenicEdit = EntityUtil.copy(scenicUpdateReq, Scenic.class);
            List<PhotoReq> photoJson = scenicUpdateReq.getPhotoJson();
            String photoStr = JSON.toJSONString(photoJson);
            scenicEdit.setPhotoJson(photoStr);
            scenicEdit.setScenicLevel(scenicUpdateReq.getScenicLevel());
            scenicEdit.setScenicLocation(scenicUpdateReq.getScenicLocation());
            scenicEdit.setModifiedId(currentUser.getId());
            scenicEdit.setGmtModified(LocalDateTime.now());
            if (scenicMapper.updateById(scenicEdit) > 0)
                return new Result(scenicEdit.getId());
        } else {
            return Result.failed(SystemError.MAINDATA_4022);
        }
        return Result.failed(new BusinessException(SystemError.MAINDATA_4022));
    }

    /**
     * 修改景点资料
     *
     * @param scenicUpdateStatusReq
     * @param currentUser
     * @return
     */
    @Override
    public Result modifyStatus(ScenicUpdateStatusReq scenicUpdateStatusReq, TokenUser currentUser) {
        QueryWrapper<Scenic> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("id", scenicUpdateStatusReq.getId());
        Scenic scenic = scenicMapper.selectOne(queryWrapper);
        if (scenic != null) {
            scenic.setStatus(scenicUpdateStatusReq.getStatus());
            scenicMapper.updateById(scenic);
            return Result.success(scenic.getId());
        }
        if (scenic == null) {
            throw new BusinessException(SystemError.MAINDATA_4021);
        }
        return Result.success();
    }

    @Override
    public Result delete(Long id, TokenUser del) {
        QueryWrapper<Scenic> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("id", id);
        queryWrapper.eq("is_deleted", 0);
        Integer count = scenicMapper.selectCount(queryWrapper);

        if (count.equals(1)) {
            Scenic scenic = new Scenic();
            scenic.setId(id);
            scenic.setIsDeleted(NumberConstant.ONE.getValue());
            if (scenicMapper.updateById(scenic) > 0)
                return Result.success(scenic.getId());
        }
        if (count.equals(0)) {
            throw new BusinessException(SystemError.MAINDATA_4019);
        }

        return Result.success();
    }


    @Override
    public Result<ScenicDTO> detail(ScenicDetailReq scenicDetailReq) {
        Scenic scenic = scenicMapper.selectById(scenicDetailReq.getId());

        if ((scenic != null) && scenic.getIsDeleted().equals(NumberConstant.ZERO.getValue())) {
            ScenicDTO scenicDetailDisplayDTO = EntityUtil.copy(scenic, ScenicDTO.class);
            return Result.success(scenicDetailDisplayDTO);

        } else {
            return Result.failed(SystemError.MAINDATA_4023);
        }
    }

    @Override
    public ScenicDTO quertByiId(String id) {
        Scenic scenic = scenicMapper.selectById(id);

        if ((scenic != null) && scenic.getIsDeleted().equals(NumberConstant.ZERO.getValue())) {
            ScenicDTO scenicDetailDisplayDTO = EntityUtil.copy(scenic, ScenicDTO.class);
            return scenicDetailDisplayDTO;

        } else {
            return null;
        }
    }


    @Override
    public PageResponse<ScenicDTO> list(ScenicListReq scenicListReq, TokenUser currentUser) {

        QueryWrapper<Scenic> wrapper = new QueryWrapper<>();

        wrapper.like(StringUtils.isNotBlank(scenicListReq.getName()), "name", scenicListReq.getName());
        if (null != scenicListReq.getAreaId() && 0 != scenicListReq.getAreaId()) {
            wrapper.eq("area_id", scenicListReq.getAreaId());
        }
        if (null != scenicListReq.getStatus() && scenicListReq.getStatus() != 2) {
            //nothing
            wrapper.eq("status", scenicListReq.getStatus());
        }
        wrapper.eq("is_deleted", 0);
        wrapper.orderByDesc("gmt_create");
        Page<Scenic> iPage = new Page<>(scenicListReq.getPageNo(), scenicListReq.getPageSize());

        iPage = scenicMapper.selectPage(iPage, wrapper);
        List<ScenicDTO> scenicDtoList = new ArrayList<>();
        iPage.getRecords().forEach(i -> {
            ScenicDTO scenicDTO = EntityUtil.copy(i, ScenicDTO.class);
            ScenicProductByIdReq req = new ScenicProductByIdReq();
            req.setId(scenicDTO.getId());
            scenicDtoList.add(scenicDTO);
        });

        PageResponse<ScenicDTO> pageResponse = new PageResponse<>(scenicDtoList, iPage.getCurrent() == 1,
                iPage.getTotal() <= (iPage.getCurrent() * iPage.getSize()), iPage.getTotal(), iPage.getCurrent(), iPage.getSize());

        return pageResponse;


    }

    public SysArea getAreaName(String areaName) {
        QueryWrapper<SysArea> queryWrapper = new QueryWrapper<SysArea>();
        queryWrapper.lambda().eq(SysArea::getProvinceTraditional, areaName);
        queryWrapper.lambda().eq(SysArea::getIsDeleted, IsDeletedCode.NO.getCode());
        queryWrapper.lambda().eq(SysArea::getStatus, IsDeletedCode.NO.getCode());
        List<SysArea> sysArea = sysAreaMapper.selectList(queryWrapper);
        if (sysArea.isEmpty()) {
            return null;
        }
        return sysArea.get(0);

    }

    public String retrieveAreaName(Long id) {
        QueryWrapper<SysArea> queryWrapper = new QueryWrapper<SysArea>();
//           Integer status=areaIdReq.getStatus();
        queryWrapper.lambda().eq(SysArea::getId, id);
//                   .eq(SysArea::getStatus,status) ;
        SysArea sysArea = sysAreaMapper.selectOne(queryWrapper);
        if (null == sysArea) {
            throw new BusinessException();
        }
        String areaStr = "";
        if (StringUtils.isNotBlank(sysArea.getCountryTraditional()))
            areaStr = areaStr + sysArea.getCountryTraditional();
        if (StringUtils.isNotBlank(sysArea.getProvinceTraditional()))
            areaStr = areaStr + "" + sysArea.getProvinceTraditional();
        if (StringUtils.isNotBlank(sysArea.getCityTraditional()))
            areaStr = areaStr + "" + sysArea.getCityTraditional();
        return areaStr;

    }


    @Override
    public List<OperationLogDTO> opeartionRecords(TokenUser currentUser) {
        QueryWrapper<OperationLog> queryWrapper = new QueryWrapper();
        queryWrapper.like("title", "景点资料");
        queryWrapper.like("description", "景点资料");
        queryWrapper.like("type", "ADD").or();
        queryWrapper.like("type", "UPDATE").or();
        queryWrapper.like("type", "DELETE");

        List<OperationLog> operationLogList = operationLogMapper.selectList(queryWrapper);
        List<OperationLogDTO> operationLogDTOList = new ArrayList<>();
        operationLogList.forEach(log -> {
            OperationLogDTO operationLogDTO = EntityUtil.copy(log, OperationLogDTO.class);
            operationLogDTOList.add(operationLogDTO);
        });
        return operationLogDTOList;
    }

    /**
     * 查询景点名称
     *
     * @param map
     * @return
     */
    @Override
    public Map<Long, String> queryScenicName(Map<Long, String> map) {
        // scenicMapper
        Map<Long, String> mapName = new HashMap<>();
        for (Long id : map.keySet()) {
            Scenic scenic = scenicMapper.selectById(id);
            if (null != scenic) {
                mapName.put(id, scenic.getName());
            }
        }
        return mapName;
    }

    @Override
    public Result saveScenic(TokenUser user) {
        String CONTENT_WITH_NO_SIGN = "{\"mer_no\":\"9000000242\",\"method\":\"chimelong.trip.park.info.get\",\"sign\":\"\",\"nonce_str\":\"80c5a87d22ed461bbe91ec691a4d9874\",\"timestamp\":\"2021-03-12 10:13:01\",\"ver_no\":\"1.0\",\"body\":\"{}}\"}";
        String signAppendStr = new APISignUtil().contentJointTest(CONTENT_WITH_NO_SIGN);
        String toData = new APIAesUtil().aesEncodeBase64(signAppendStr, "1d70b9997df4946824810ebb069dbe28");//SIGN_KEY:"1d70b9997df4946824810ebb069dbe28"（长隆提供）
        String params =
                "{" +
                        "\"mer_no\":\"9000000242\"," +
                        "\"data\":\"" + toData + "\"" +
                        "}";
        String contentType = "application/json;charset=utf-8";
        String path = "http://47.244.225.190:8080/hub/product/ota/call2/gsa/chimelong/api.do";
        String returnStr = new APIAesUtil().aesDecodeBase64(APIUtil.callAPIFunc(contentType, path, params, "POST"), "1d70b9997df4946824810ebb069dbe28");
        System.out.println(returnStr);
        cn.hutool.json.JSONObject j = new JSONObject(returnStr);
        JSONArray parkData = j.getJSONObject("body").getJSONArray("parkData");
        List<ChimeLongScenicDTO> chimeLongScenicDTOs = (List<ChimeLongScenicDTO>) JSON.parseArray(String.valueOf(parkData), ChimeLongScenicDTO.class);
        for (ChimeLongScenicDTO scenicDTO : chimeLongScenicDTOs) {
            Scenic scenic = new Scenic();
            JSONObject jsonScenicName = new JSONObject(scenicDTO.getParkName());
            scenic.setName(jsonScenicName.get("zh").toString());
            scenic.setGmtCreate(LocalDateTime.now());
            scenic.setCreateId(user.getId());
            JSONObject introduce = new JSONObject(scenicDTO.getDescription());
            scenic.setIntroduce(introduce.get("zh").toString());
            scenic.setScenicLevelId((long) scenicDTO.getStarRate());
            JSONObject adress = new JSONObject(scenicDTO.getAddress());
            scenic.setScenicLocation(adress.get("zh").toString());
            if ("GZ".equals(scenicDTO.getRegionId())) {
                scenic.setAreaName(ScenicEnum.GZ.getName());
            } else if ("ZH".equals(equals(scenicDTO.getRegionId()))) {
                scenic.setAreaName(ScenicEnum.ZH.getName());
            } else if ("ZH".equals(equals(scenicDTO.getRegionId()))) {
                scenic.setAreaName(ScenicEnum.QY.getName());
            }
            if (scenic.getAreaName() != null) {
                AreaQueryReq areaQueryReq = new AreaQueryReq();
                areaQueryReq.setName(scenic.getAreaName());
                areaQueryReq.setStatus(0);
                AreaDTO areaDTO = sysAreaService.query(areaQueryReq);
                scenic.setAreaId(areaDTO.getId());
            }
            scenicMapper.insert(scenic);
        }
        return Result.success();
    }


    @Override
    public Result<List<ScenicDTO>> quertByids(String ids) {
        List<Scenic> scenicList = new ArrayList<>();
        if (StringUtils.isNotBlank(ids)) {
            scenicList = scenicMapper.quertByids(ids);
            for (Scenic scenic : scenicList) {
                scenic.setPhotoJson(null);
                scenic.setAdmissionNotes(null);
            }
        }
        List<ScenicDTO> scenicDTOList = new ArrayList<>();
        if(CollectionUtils.isNotEmpty(scenicList)){
            scenicDTOList = EntityUtil.copyList(scenicList, ScenicDTO.class);
        }
        return Result.success(scenicDTOList);
    }


}